home *** CD-ROM | disk | FTP | other *** search
/ Internet Info 1994 March / Internet Info CD-ROM (Walnut Creek) (March 1994).iso / networking / ip / ka9q / net_src.arc / ax25dump.c < prev    next >
Encoding:
C/C++ Source or Header  |  1989-05-08  |  6.4 KB  |  271 lines

  1. #include <stdio.h>
  2. #include "global.h"
  3. #include "mbuf.h"
  4. #include "ax25.h"
  5. #include "timer.h"
  6. #include "lapb.h"
  7. #include "trace.h"
  8.  
  9. extern FILE *trfp;
  10.  
  11. /* Dump an AX.25 packet header */
  12. ax25_dump(bpp,check)
  13. struct mbuf **bpp;
  14. int check;    /* Not used */
  15. {
  16.     char *decode_type();
  17.     char tmp[20];
  18.     char control,pid;
  19.     int16 type,ftype();
  20.     struct ax25 hdr;
  21.     struct ax25_addr *hp;
  22.  
  23.     fprintf(trfp,"AX25: ");
  24.     /* Extract the address header */
  25.     if(ntohax25(&hdr,bpp) < 0){
  26.         /* Something wrong with the header */
  27.         fprintf(trfp," bad header!\n");
  28.         return;
  29.     }
  30.     pax25(tmp,&hdr.source);
  31.     fprintf(trfp,"%s",tmp);
  32.     pax25(tmp,&hdr.dest);
  33.     fprintf(trfp,"->%s",tmp);
  34.     if(hdr.ndigis > 0){
  35.         fprintf(trfp," v");
  36.         for(hp = &hdr.digis[0]; hp < &hdr.digis[hdr.ndigis]; hp++){
  37.             /* Print digi string */
  38.             pax25(tmp,hp);
  39.             fprintf(trfp," %s%s",tmp,(hp->ssid & REPEATED) ? "*":"");
  40.         }
  41.     }
  42.     if(pullup(bpp,&control,1) != 1)
  43.         return;
  44.  
  45.     putchar(' ');
  46.     type = ftype(control);
  47.     fprintf(trfp,"%s",decode_type(type));
  48.     /* Dump poll/final bit */
  49.     if(control & PF){
  50.         switch(hdr.cmdrsp){
  51.         case COMMAND:
  52.             fprintf(trfp,"(P)");
  53.             break;
  54.         case RESPONSE:
  55.             fprintf(trfp,"(F)");
  56.             break;
  57.         default:
  58.             fprintf(trfp,"(P/F)");
  59.             break;
  60.         }
  61.     }
  62.     /* Dump sequence numbers */
  63.     if((type & 0x3) != U)    /* I or S frame? */
  64.         fprintf(trfp," NR=%d",(control>>5)&7);
  65.     if(type == I || type == UI){    
  66.         if(type == I)
  67.             fprintf(trfp," NS=%d",(control>>1)&7);
  68.         /* Decode I field */
  69.         if(pullup(bpp,&pid,1) == 1){    /* Get pid */
  70.             switch(pid & (PID_FIRST | PID_LAST)){
  71.             case PID_FIRST:
  72.                 fprintf(trfp," First frag");
  73.                 break;
  74.             case PID_LAST:
  75.                 fprintf(trfp," Last frag");
  76.                 break;
  77.             case PID_FIRST|PID_LAST:
  78.                 break;    /* Complete message, say nothing */
  79.             case 0:
  80.                 fprintf(trfp," Middle frag");
  81.                 break;
  82.             }
  83.             fprintf(trfp," pid=");
  84.             switch(pid & 0x3f){
  85.             case PID_ARP:
  86.                 fprintf(trfp,"ARP\n");
  87.                 break;
  88.             case PID_NETROM:
  89.                 fprintf(trfp,"NET/ROM\n");
  90.                 break;
  91.             case PID_IP:
  92.                 fprintf(trfp,"IP\n");
  93.                 break;
  94.             case PID_NO_L3:
  95.                 fprintf(trfp,"Text\n");
  96.                 break;
  97.             default:
  98.                 fprintf(trfp,"0x%x\n",pid);
  99.             }
  100.             /* Only decode frames that are the first in a
  101.              * multi-frame sequence
  102.              */
  103.             switch(pid & (PID_PID | PID_FIRST)){
  104.             case PID_ARP | PID_FIRST:
  105.                 arp_dump(bpp);
  106.                 break;
  107.             case PID_IP | PID_FIRST:
  108.                 /* Only checksum complete frames */
  109.                 ip_dump(bpp,pid & PID_LAST);
  110.                 break;
  111.             case PID_NETROM | PID_FIRST:
  112.                 netrom_dump(bpp);
  113.                 break;
  114.             }
  115.         }
  116.     } else if(type == FRMR && pullup(bpp,tmp,3) == 3){
  117.         fprintf(trfp,": %s",decode_type(ftype(tmp[0])));
  118.         fprintf(trfp," Vr = %d Vs = %d",(tmp[1] >> 5) & MMASK,
  119.             (tmp[1] >> 1) & MMASK);
  120.         if(tmp[2] & W)
  121.             fprintf(trfp," Invalid control field");
  122.         if(tmp[2] & X)
  123.             fprintf(trfp," Illegal I-field");
  124.         if(tmp[2] & Y)
  125.             fprintf(trfp," Too-long I-field");
  126.         if(tmp[2] & Z)
  127.             fprintf(trfp," Invalid seq number");
  128.         fprintf(trfp,"\n");
  129.     } else
  130.         fprintf(trfp,"\n");
  131.  
  132.     fflush(stdout);
  133. }
  134. /* Display NET/ROM network and transport headers */
  135. static
  136. netrom_dump(bpp)
  137. struct mbuf **bpp;
  138. {
  139.     struct ax25_addr src,dest;
  140.     char x;
  141.     char tmp[16];
  142.     char thdr[5];
  143.     register i;
  144.  
  145.     if(bpp == NULLBUFP || *bpp == NULLBUF)
  146.         return;
  147.     /* See if it is a routing broadcast */
  148.     if(uchar(*(*bpp)->data) == 0xff) {
  149.         pullup(bpp,tmp,1);        /* Signature */
  150.         pullup(bpp,tmp,ALEN);
  151.         tmp[ALEN] = '\0';
  152.         fprintf(trfp,"NET/ROM Routing: %s\n",tmp);
  153.         for(i = 0;i < 11;i++) {
  154.             if (pullup(bpp,tmp,AXALEN) < AXALEN)
  155.                 break;
  156.             memcpy(src.call,tmp,ALEN);
  157.             src.ssid = tmp[ALEN];
  158.             pax25(tmp,&src);
  159.             fprintf(trfp,"        %12s",tmp);
  160.             pullup(bpp,tmp,ALEN);
  161.             tmp[ALEN] = '\0';
  162.             fprintf(trfp,"%8s",tmp);
  163.             pullup(bpp,tmp,AXALEN);
  164.             memcpy(src.call,tmp, ALEN);
  165.             src.ssid = tmp[ALEN];
  166.             pax25(tmp,&src);
  167.             fprintf(trfp,"    %12s", tmp);
  168.             pullup(bpp,tmp,1);
  169.             fprintf(trfp,"    %3u\n", (unsigned)uchar(tmp[0]));
  170.         }
  171.         return;
  172.     }
  173.     /* Decode network layer */
  174.     pullup(bpp,tmp,AXALEN);
  175.     memcpy(src.call,tmp,ALEN);
  176.     src.ssid = tmp[ALEN];
  177.     pax25(tmp,&src);
  178.     fprintf(trfp,"NET/ROM: %s",tmp);
  179.  
  180.     pullup(bpp,tmp,AXALEN);
  181.     memcpy(dest.call,tmp,ALEN);
  182.     dest.ssid = tmp[ALEN];
  183.     pax25(tmp,&dest);
  184.     fprintf(trfp,"->%s",tmp);
  185.  
  186.     pullup(bpp,&x,1);
  187.     fprintf(trfp," ttl %d\n",uchar(x));
  188.  
  189.     /* Read first five bytes of "transport" header */
  190.     pullup(bpp,thdr,5);
  191.     switch(thdr[4] & 0xf){
  192.     case 0:    /* network PID extension */
  193.         if (thdr[0] == PID_IP && thdr[1] == PID_IP)
  194.             ip_dump(bpp,1) ;
  195.         else
  196.             fprintf(trfp,"         protocol family %x, proto %x",
  197.                     uchar(thdr[0]), uchar(thdr[1])) ;
  198.         break ;
  199.     case 1:    /* Connect request */
  200.         fprintf(trfp,"         conn rqst: ckt %d/%d",uchar(thdr[0]),uchar(thdr[1]));
  201.         pullup(bpp,&x,1);
  202.         fprintf(trfp," wnd %d",x);
  203.         pullup(bpp,(char *)&src,sizeof(struct ax25_addr));
  204.         pax25(tmp,&src);
  205.         fprintf(trfp," %s",tmp);
  206.         pullup(bpp,(char *)&dest,sizeof(struct ax25_addr));
  207.         pax25(tmp,&dest);
  208.         fprintf(trfp,"->%s",tmp);
  209.         break;
  210.     case 2:    /* Connect acknowledgement */
  211.         fprintf(trfp,"         conn ack: ur ckt %d/%d my ckt %d/%d",
  212.             uchar(thdr[0]), uchar(thdr[1]), uchar(thdr[2]),
  213.             uchar(thdr[3]));
  214.         pullup(bpp,&x,1);
  215.         fprintf(trfp," wnd %d",x);
  216.         break;
  217.     case 3:    /* Disconnect request */
  218.         fprintf(trfp,"         disc: ckt %d/%d",uchar(thdr[0]),uchar(thdr[1]));
  219.         break;
  220.     case 4:    /* Disconnect acknowledgement */
  221.         fprintf(trfp,"         disc ack: ckt %d/%d",uchar(thdr[0]),uchar(thdr[1]));
  222.         break;
  223.     case 5:    /* Information (data) */
  224.         fprintf(trfp,"         info: ckt %d/%d",uchar(thdr[0]),uchar(thdr[1]));
  225.         fprintf(trfp," txseq %d rxseq %d",uchar(thdr[2]), uchar(thdr[3]));
  226.         break;
  227.     case 6:    /* Information acknowledgement */
  228.         fprintf(trfp,"         info ack: ckt %d/%d rxseq %d",
  229.                 uchar(thdr[0]),uchar(thdr[1]),uchar(thdr[3]));
  230.         break;
  231.     default:
  232.         fprintf(trfp,"         unknown transport type %d", thdr[4] & 0x0f) ;
  233.         break;
  234.     }
  235.     if(thdr[4] & 0x80)
  236.         fprintf(trfp," CHOKE");
  237.     if(thdr[4] & 0x40)
  238.         fprintf(trfp," NAK");
  239.     fprintf(trfp,"\n");
  240. }
  241. char *
  242. decode_type(type)
  243. int16 type;
  244. {
  245.     switch(uchar(type)){
  246.     case I:
  247.         return "I";
  248.     case SABM:
  249.         return "SABM";
  250.     case DISC:
  251.         return "DISC";
  252.     case DM:
  253.         return "DM";
  254.     case UA:
  255.         return "UA";
  256.     case RR:
  257.         return "RR";
  258.     case RNR:
  259.         return "RNR";
  260.     case REJ:
  261.         return "REJ";
  262.     case FRMR:
  263.         return "FRMR";
  264.     case UI:
  265.         return "UI";
  266.     default:
  267.         return "[invalid]";
  268.     }
  269. }
  270.  
  271.